package com.topisv.tms.service;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.ui.Model;

import com.topisv.tms.costants.CustomersConstants;
import com.topisv.tms.entity.Customers;
import com.topisv.tms.entity.EdiGoodsSku;
import com.topisv.tms.entity.User;
import com.topisv.tms.entity.WarehouseArea;
import com.topisv.tms.entity.WarehouseTransfer;
import com.topisv.tms.entity.stock.CusStock;
import com.topisv.tms.mybatis.service.CommonService;
import com.topisv.tms.repository.CustomersDao;
import com.topisv.tms.repository.EdiGoodsSkuDao;
import com.topisv.tms.repository.UserDao;
import com.topisv.tms.repository.WarehouseAreaDao;
import com.topisv.tms.rest.qimen.qmentity.request.deliveryorder.DeliveryOrderItem;
import com.topisv.tms.rest.qimen.qmentity.request.deliveryorder.DeliveryOrderRequest;
import com.topisv.tms.service.account.ShiroDbRealm.ShiroUser;
import com.topisv.tms.utils.PubUtil;
import com.topisv.tms.vo.warehouse.WarehouseAreaVo;
import com.topisv.tms.vo.warehouse.WarehouseOrderVo;
/**
 * 
 *
 * @author yuansheng
 * @version 1.0.0
 */
@Service
public class WarehouseAreaService extends CommonService {
	
	private static final Logger log = LoggerFactory.getLogger(WarehouseAreaService.class);
	
    @Autowired
    private CustomersDao customersDao;
    @Autowired
    private WarehouseAreaDao warehouseAreaDao;
    @Autowired
    private UserDao userDao;
    @Autowired
    private EdiGoodsSkuDao ediGoodsSkuDao;

    public void distributeWarehouse(Long id, String state, Model model) {
        // 获取商家
        Customers customer = customersDao.findOne(id);
        // 获取仓库列表
        List list = sqlMapDao.getSqlSession().selectList("warehouseAreaMapper.findWarehouseList", customer);
        List<WarehouseAreaVo> warehouses = PubUtil.convertListMapToObject(list, WarehouseAreaVo.class);
        for (WarehouseAreaVo warehouseAreaVo : warehouses) {
            String isPrimary = warehouseAreaVo.getWarehouseCode().equals(customer.getPrimeWarehouseCode()) ? "1" : "0";
            warehouseAreaVo.setIsPrimary(isPrimary);
        }
        model.addAttribute("customer", customer);

        model.addAttribute("warehouseList", warehouses);

        model.addAttribute("distributeWarehouseState", state);
    }

    public WarehouseArea findByWarehouseAndArea(String customerCode, String warehouseCode, String province, String city) {
        WarehouseArea area = new WarehouseArea();
        area.setCustomerCode(customerCode);
        area.setWarehouseCode(warehouseCode);
        area.setProvince(province);
        area.setCity(city);
        WarehouseArea result = sqlMapDao.getSqlSession().selectOne("warehouseAreaMapper.findByWarehouseAndArea", area);
        return result;
    }

    public List<WarehouseArea> findCoverageArea(String warehouseCode, String customerCode) {
        return warehouseAreaDao.findByWarehouseAndCustomer(warehouseCode, customerCode);
    }

    @Transactional(readOnly = false)
    public void addCoverageArea(String customerCode, String warehouseCode, String SelectProvince, String SelectCity) {
        WarehouseArea warehouseArea = findByWarehouseAndArea(customerCode,warehouseCode, SelectProvince, SelectCity);
        if (warehouseArea == null) {
            ShiroUser curUser = (ShiroUser) SecurityUtils.getSubject().getPrincipal();
            User user = userDao.findByJobuuid(curUser.jobuuid);
            
            WarehouseArea area = new WarehouseArea();
            area.setCustomerCode(customerCode);
            area.setWarehouseCode(warehouseCode);
            area.setProvince(SelectProvince);
            area.setCity(SelectCity);
            area.setCreateTime(new Date());
            area.setCreatorName(user.getRealname());
            area.setCreatorCode(user.getUsername());
            warehouseAreaDao.save(area);
        }
    }

    @Transactional(readOnly = false)
    public void deleteCoverageArea(Long id) {
        warehouseAreaDao.delete(id);
    }
    
    /**
     * 根据报文返回所分配的仓库编码
     *
     * @param 
     * @return 
     * @throws 
     * @author yuansheng
     * @version 1.0.0
     */
    public String distributeOrder(DeliveryOrderRequest request){
        // 1.判断是否开启分仓
        Customers customer = customersDao.findByCustomerCode(request.getDeliveryOrderItems().get(0).getOwnerCode());
        if (!CustomersConstants.OPEN_DISTRIBUTION.equals(customer.getDistributeWarehouseState())) {
            // 未启用，返回报文中的
        	log.info("=================客户未启用分仓:" + request.getDeliveryOrder().getDeliveryOrderCode());
            return request.getDeliveryOrder().getWarehouseCode();
        }
        
        // 2.根据覆盖区查找仓库
        WarehouseOrderVo order = new WarehouseOrderVo();
        if (StringUtils.isNotBlank(request.getDeliveryOrder().getReceiverInfo().getProvince())) {
        	order.setProvince(request.getDeliveryOrder().getReceiverInfo().getProvince());
		}
        if (StringUtils.isNotBlank(request.getDeliveryOrder().getReceiverInfo().getCity())) {
        	order.setCity(request.getDeliveryOrder().getReceiverInfo().getCity());
        }
        order.setCustomerCode(request.getDeliveryOrderItems().get(0).getOwnerCode());
        // 先按城市匹配，找不到再匹配省份
        List areas = null;
        if (StringUtils.isNotBlank(order.getCity())) {
        	areas = sqlMapDao.getSqlSession().selectList("warehouseAreaMapper.findOrderWarehouseByCity", order);
		}
        if (PubUtil.isEmpty(areas) && StringUtils.isNotBlank(order.getProvince())) {
        	areas = sqlMapDao.getSqlSession().selectList("warehouseAreaMapper.findOrderWarehouseByProvince", order);
		}
        if (PubUtil.isEmpty(areas)) { // 如果没有找到，使用默认仓
        	log.info("=================2.根据覆盖区查找仓库" + request.getDeliveryOrder().getDeliveryOrderCode());
            return customer.getPrimeWarehouseCode();
        }
        List<WarehouseOrderVo> warehouses = PubUtil.convertListMapToObject(areas, WarehouseOrderVo.class);
        // 3.查询此仓库是否库存充足
        order.setWarehouseCode(warehouses.get(0).getWarehouseCode());
        // 查询sku_id
        /*Map<String, String> skuIds = findAllSkuId(request.getDeliveryOrderItems());
        // 转换sku_bar为sku_id
        List<DeliveryOrderItem> items = new ArrayList<DeliveryOrderItem>();
        for (String key : skuIds.keySet()) {
			DeliveryOrderItem item = new DeliveryOrderItem();
			item.setItemId(key);
			item.setItemCode(skuIds.get(key)); // 设置itemCode为sku_id，而不是原来的sku_bar
			item.setPlanQty(sk);
			items.add(item);
		}*/
        order.setItems(copyItems(request.getDeliveryOrderItems()));
        List<CusStock> stocks = sqlMapDao.getSqlSession().selectList("warehouseAreaMapper.findOrderSalasNum", order);
        if (verifyStock(order.getItems() , stocks)) {
            // 匹配到的仓有库存，直接返回到此仓库
        	log.info("=================匹配到的仓有库存，直接返回到此仓库" + request.getDeliveryOrder().getDeliveryOrderCode());
            return order.getWarehouseCode();
        }
        // 4.如果覆盖区下的父级仓库库存不足，查找所有流转仓
        List<WarehouseTransfer> trans = sqlMapDao.getSqlSession().selectList("warehouseAreaMapper.findOrderWarehouseByLevel", order);
        // 5.如果没有流转仓就返回默认仓
        if (trans == null || trans.size() <= 0) {
        	log.info("=================5.如果没有流转仓就返回默认仓" + request.getDeliveryOrder().getDeliveryOrderCode());
            return customer.getPrimeWarehouseCode();
        }
        // 6.循环遍历流转仓，找到匹配的则返回
        // List<WarehouseTransfer> transfers = PubUtil.convertListMapToObject(trans, WarehouseTransfer.class);
        for (WarehouseTransfer warehouseTransfer : trans) {
            order.setWarehouseCode(warehouseTransfer.getTransferWarehouseCode());
            List<CusStock> astocks = sqlMapDao.getSqlSession().selectList("warehouseAreaMapper.findOrderSalasNum", order);
            if (verifyStock(order.getItems(), astocks)) {
            	log.info("=================6.循环遍历流转仓，找到匹配的则返回:" + warehouseTransfer.getTransferWarehouseCode() + "," + request.getDeliveryOrder().getDeliveryOrderCode());
                return warehouseTransfer.getTransferWarehouseCode();
            }
        }
        // 7.如果流转仓都不满足，则使用默认仓
        log.info("=================7.如果流转仓都不满足，则使用默认仓" + request.getDeliveryOrder().getDeliveryOrderCode());
        return customer.getPrimeWarehouseCode();
    }
    
    /**
     * 查找所有sku_id
     *
     * @param 
     * @return 
     * @throws 
     * @author yuansheng
     * @version 1.0.0
     */
    public List<DeliveryOrderItem> copyItems(List<DeliveryOrderItem> deliveryOrderItems) {
    	// key=edi_goods_sku 主键id value=sku_id
    	/*Map<String, String> skuIds = new HashMap<String, String>();
    	for (DeliveryOrderItem deliveryOrderItem : deliveryOrderItems) {
			EdiGoodsSku sku = ediGoodsSkuDao.findOne(Long.valueOf(deliveryOrderItem.getItemId()));
			skuIds.put(deliveryOrderItem.getItemId(), sku.getSku());
		}*/
        List<DeliveryOrderItem> items = new ArrayList<DeliveryOrderItem>();
    	for (DeliveryOrderItem deliveryOrderItem : deliveryOrderItems) {
            EdiGoodsSku sku = ediGoodsSkuDao.findOne(Long.valueOf(deliveryOrderItem.getItemId()));
            DeliveryOrderItem item = new DeliveryOrderItem();
            item.setItemId(deliveryOrderItem.getItemId());
            item.setItemCode(sku.getSku()); // 设置itemCode为sku_id，而不是原来的sku_bar
            item.setPlanQty(deliveryOrderItem.getPlanQty());
            items.add(item);
        }
		return items;
    }
    
    
    /**
     * 订单库存校验方法
     *
     * @param 
     * @return 
     * @throws 
     * @author yuansheng
     * @version 1.0.0
     */
    private boolean verifyStock(List<DeliveryOrderItem> items,List<CusStock> stocks){
        boolean hasStock = true;
        for (DeliveryOrderItem item : items) {
            boolean flag = false;
            for (CusStock cusStock : stocks) {
                if (cusStock.getSku().equals(item.getItemCode()) && (cusStock.getSalesNum() - cusStock.getLockedNum()) >= item.getPlanQty()) {
                    flag = true;
                    break;
                }
            }
            if (!flag) {
                // 库存不足
                hasStock = false;
                break;
            }
        }
        
        return hasStock;
    }
    /*private boolean verifyStock(List<DeliveryOrderItem> items,List<CusStock> stocks, Map<String, String> skuIds){
        boolean hasStock = true;
        for (DeliveryOrderItem item : items) {
            boolean flag = false;
            for (CusStock cusStock : stocks) {
                String skuId = skuIds.get(item.getItemId());
                if (cusStock.getSku().equals(anObject)) && (cusStock.getSalesNum() - cusStock.getLockedNum()) >= item.getPlanQty()) {
                    flag = true;
                    break;
                }
            }
            if (!flag) {
                // 库存不足
                hasStock = false;
                break;
            }
        }
        
        return hasStock;
    }*/
    
}
